package com.itheima.interceptor;

import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


/**
 * 拦截器(Interceptor)
 * 概念：是一种动态拦截方法调用的机制，类似于过滤器。Spring框架中提供的，用来动态拦截控制器方法的执行。请求会先被过滤器拦截,通过之后调用方法前才会被拦截器拦截.
 * 作用：拦截请求，在指定的方法调用前后，根据业务需要执行预先设定的代码。
 * <p>
 * 添加Interceptor的过程:
 * 1.定义拦截器，实现HandlerInterceptor接口，并重写其所有方法。
 * 2.注册拦截器
 */

/*
Filter 与 Interceptor执行流程

           (Filter)                            (Interceptor)
       -> 放行前逻辑 ->                    ->    preHandle     ->
浏览器     doFilter()   DispatcherServlet       postHandle         Controller
       <- 放行后逻辑 <-                    <-  afterCompletion <-
         {---Tomcat---} {----------------------SpringMVC------------------}
         {------------------------------Web服务器-------------------------}
 */

/*
Filter 与 Interceptor的区别

接口规范不同：过滤器需要实现Filter接口，而拦截器需要实现HandlerInterceptor接口。
拦截范围不同：过滤器Filter会拦截所有的资源，而Interceptor只会拦截SpringMVC环境中的资源。



过滤器(Filter) 是JavaEE提供的,实现的是 javax.servlet.Filter 接口，而这个接口是在Servlet规范中定义的，也就是说过滤器Filter 的使用要依赖于Tomcat等容器，导致它只能在web程序中使用。
拦截器(Interceptor) 它是一个Spring组件，并由Spring容器管理，并不依赖Tomcat等容器，是可以单独使用的。不仅能应用在web程序中，也可以用于Application、Swing等程序中。

过滤器Filter是在请求进入容器后，但在进入servlet之前进行预处理，请求结束是在servlet处理完以后。
拦截器 Interceptor 是在请求进入servlet后，在进入Controller之前进行预处理的，Controller 中渲染了对应的视图之后请求结束。

拦截器可以访问action上下文、值栈里的对象，而过滤器不能访问。

在action的生命周期中，拦截器可以多次被调用，而过滤器只能在容器初始化时被调用一次。

拦截器可以获取IOC容器中的各个bean，而过滤器就不行，这点很重要，在拦截器里注入一个service，可以调用业务逻辑。拦截器可以获取ioc中的service bean实现业务逻辑。
————————————————
版权声明：本文为CSDN博主「何以解忧，唯有..」的原创文章，遵循CC 4.0 BY-SA版权协议，转载请附上原文出处链接及本声明。
原文链接：https://blog.csdn.net/KevinChen2019/article/details/127537209
 */
@Component //表示该类归SpringBoot管理
@Slf4j
public class LoginInterceptor implements HandlerInterceptor {

    //调用方法前执行,返回true放行，返回false不放行
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {

        log.info("拦截器拦截住了,方法调用前执行");

        return true;
    }

    //调用方法后执行
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        log.info("拦截器拦截住了,方法调用后执行");
    }

    //在调用方法完成整个请求结束， DispatcherServlet 渲染了对应的视图之后执行。
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        log.info("拦截器拦截住了,方法全部执行完毕后执行");
    }
}
